package namensdienst;

import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.net.Socket;
import java.util.Hashtable;

import mware_lib.RemoteException;
import mware_lib.communication.messRebind;


public class NSConnectionTreatment extends Thread {
	private Socket socket;
	private Object objectReceived;
	private static Hashtable<String, NameServiceRemoteObject> listRemoteObjects=new Hashtable<String, NameServiceRemoteObject>();

	public NSConnectionTreatment(Socket socketReceived) {
		this.socket = socketReceived;
	}
	
	public void run()
	{
		ObjectOutputStream out;
        ObjectInputStream in;
        try {
               in = new ObjectInputStream(socket.getInputStream());
               out = new ObjectOutputStream(socket.getOutputStream());
               objectReceived = in.readObject();
               //treat received message with rebind or with resolve
               Object toSend=checkObject(objectReceived);
                       
                out.writeObject(toSend);
                in.close();
                out.close();
                socket.close();
                
        } catch (IOException e) {
                System.err.println("namensdienst.NSConnectionTreatment exception: " + e.getMessage());
        } catch (ClassNotFoundException e) {
                System.err.println("namensdienst.NSConnectionTreatment exception: " + e.getMessage());
        } catch (RemoteException e) {
        	System.err.println(e.getMessage());
        }
	}

	private Object checkObject(Object objectReceived) throws RemoteException {
		try{
            if(objectReceived instanceof messRebind)
            {
                    messRebind mess = (messRebind) objectReceived;                   
                    if(mess.getTypeof().equals("rebind")) //message coming from rebind()
                    {
                    	NameServiceRemoteObject nsrObj = new  NameServiceRemoteObject();
                    	nsrObj.object = mess.getToTransmit();
						nsrObj.objectID = mess.getName();
						nsrObj.host = socket.getInetAddress().getCanonicalHostName();
						nsrObj.port = mess.getPort();
						nsrObj.type=mess.result;
						if(!(listRemoteObjects.containsKey(mess.getName())))
						{
							listRemoteObjects.put(mess.getName(), nsrObj);
							System.out.println("Added: " + nsrObj.type.getName() + " " 
							+ nsrObj.objectID + " " + nsrObj.host + "/" + nsrObj.port);
						}
						return true;
                    }
                    else if(mess.getTypeof().equals("resolve"))//message coming from resolve()
                    {
                        messRebind toSend=null; 
                    	NameServiceRemoteObject nsrObj = new  NameServiceRemoteObject();
                    	if(listRemoteObjects.containsKey(mess.getName()))
						{
                    		nsrObj= listRemoteObjects.get(mess.getName());
						}
                    	if (nsrObj != null)
                    	{
                    		toSend= new messRebind(nsrObj,mess.getName(), nsrObj.host, nsrObj.port, nsrObj.type);
                    	}
                    	return toSend;
                    }
            }
            else
            {
                    throw new RemoteException("Unknown object in namensdienst.NamensdienstData");
            }
		}catch(Exception e){
            throw new RemoteException();
		}
		return objectReceived;		
	}

	/**
	 * @return the listRemoteObjects
	 */
	public Hashtable<String, NameServiceRemoteObject> getListRemoteObjects() {
		return listRemoteObjects;
	}

	/**
	 * @param listRemoteObjects the listRemoteObjects to set
	 */
	public void setListRemoteObjects(
			Hashtable<String, NameServiceRemoteObject> listRemoteObjects) {
		NSConnectionTreatment.listRemoteObjects = listRemoteObjects;
	}

}
